using System;
using System.Data;
using System.Data.SqlClient;

namespace Dbam.DbFramework
{
	/// <summary>
	/// Factory for creating commands, connections, and parameters for Sql Server databases.
	/// </summary>
	public class SqlDbFactory
		: DbFactoryBase
	{
		/// <summary>
		/// Initialize the Sql Server database factory.
		/// </summary>
		/// <param name="connectionString"></param>
		public SqlDbFactory(string connectionString)
			: base(connectionString)
		{
		}

		/// <summary>
		/// Create a connection class compatible with Sql Server.
		/// </summary>
		/// <param name="connectionString">Connection string to the database.</param>
		/// <returns>The connection to the database.</returns>
		protected override IDbConnection CreateConnection(string connectionString)
		{
			SqlConnection connection = new SqlConnection(connectionString);
			return connection;
		}

		/// <summary>
		/// Creates a compatible parameter object for Sql Server.
		/// </summary>
		/// <param name="name">Name of the parameter.</param>
		/// <param name="type">Data type of the parameter.</param>
		/// <param name="direction">Direction of the parameter.</param>
		/// <param name="value">Value to assign the parameter.</param>
		/// <returns>A compatible Sql Server command parameter.</returns>
		public override IDataParameter CreateParam(string name, DbType type, ParameterDirection direction, object value)
		{
			SqlParameter param = new SqlParameter();
			param.ParameterName = name;
			param.DbType = type;
			param.Direction = direction;
			param.Value = value;
			return param;
		}

		/// <summary>
		/// Creates a compatible adapter for Sql Server.
		/// </summary>
		/// <param name="selectCommand">The select command.</param>
		/// <param name="insertCommand">The insert command.</param>
		/// <param name="updateCommand">The update command.</param>
		/// <param name="deleteCommand">The delete command.</param>
		/// <returns>A compatible data adapter.</returns>
		public override IDataAdapter CreateAdapter(IDbCommand selectCommand, IDbCommand insertCommand, IDbCommand updateCommand, IDbCommand deleteCommand)
		{
			if(selectCommand != null && !(selectCommand is SqlCommand))
				throw new ArgumentException(ErrorStrings.IncorrectCommandType);
			if(insertCommand != null && !(insertCommand is SqlCommand))
				throw new ArgumentException(ErrorStrings.IncorrectCommandType);
			if(updateCommand != null && !(updateCommand is SqlCommand))
				throw new ArgumentException(ErrorStrings.IncorrectCommandType);
			if(deleteCommand != null && !(deleteCommand is SqlCommand))
				throw new ArgumentException(ErrorStrings.IncorrectCommandType);

			SqlDataAdapter adapter = new SqlDataAdapter();
			adapter.SelectCommand = selectCommand as SqlCommand;
			adapter.InsertCommand = insertCommand as SqlCommand;
			adapter.UpdateCommand = updateCommand as SqlCommand;
			adapter.DeleteCommand = deleteCommand as SqlCommand;
			return adapter;
		}

		/// <summary>
		/// Creates a compatible command object for Sql Server.
		/// </summary>
		/// <param name="connection">The connection to the Sql Server database.</param>
		/// <param name="commandText">The command text.</param>
		/// <returns>A compatible command object.</returns>
		protected override IDbCommand CreateCommandCore(IDbConnection connection, string commandText)
		{
			SqlCommand command = new SqlCommand(commandText, connection as SqlConnection);
			return command;
		}
	}
}